"""
pytest configuration file for RedFire system tests
使用现有Docker数据库系统进行测试
"""
import os
import pytest
import asyncio
from typing import Generator, AsyncGenerator
from unittest.mock import MagicMock
from sqlalchemy.ext.asyncio import AsyncSession, create_async_engine, async_sessionmaker
from sqlalchemy.orm import sessionmaker
from sqlalchemy import create_engine

# 设置测试环境
os.environ['REDFIRE_ENV'] = 'test'
os.environ['TESTING'] = 'true'

# 导入配置
from backend.redfire_framework.core.config import get_service_settings
from backend.redfire_framework.core.database import DatabaseManager


# ======================================
# 🗄️ 数据库测试配置
# ======================================

@pytest.fixture(scope="session")
def test_database_config() -> dict:
    """测试数据库配置 - 使用统一配置"""
    return {
        'type': 'mysql',
        'host': os.getenv('MYSQL_HOST', 'localhost'),
        'port': int(os.getenv('MYSQL_PORT', '3307')),
        'user': os.getenv('MYSQL_USER', 'redfire_app'),
        'password': os.getenv('MYSQL_PASSWORD', 'redfire_app_2025'),
        'database': os.getenv('MYSQL_DATABASE', 'redfire_trading_test'),
        'pool_size': 2,
        'max_overflow': 5,
        'echo': True if os.getenv('DEBUG') == 'true' else False
    }


@pytest.fixture(scope="session")
def test_postgres_config() -> dict:
    """PostgreSQL测试数据库配置"""
    return {
        'type': 'postgresql',
        'host': os.getenv('POSTGRES_HOST', 'localhost'),
        'port': int(os.getenv('POSTGRES_PORT', '5432')),
        'user': os.getenv('POSTGRES_USER', 'redfire_analytics'),
        'password': os.getenv('POSTGRES_PASSWORD', 'redfire_pg_2025'),
        'database': os.getenv('POSTGRES_DATABASE', 'redfire_analytics_test'),
        'pool_size': 2,
        'max_overflow': 5,
        'echo': True if os.getenv('DEBUG') == 'true' else False
    }


@pytest.fixture(scope="session")
def database_manager(test_database_config):
    """数据库管理器"""
    manager = DatabaseManager(test_database_config)
    yield manager
    manager.close()


@pytest.fixture(scope="session")
def postgres_manager(test_postgres_config):
    """PostgreSQL数据库管理器"""
    manager = DatabaseManager(test_postgres_config)
    yield manager
    manager.close()


# ======================================
# 🔄 数据库会话
# ======================================

@pytest.fixture
async def async_db_session(database_manager) -> AsyncGenerator[AsyncSession, None]:
    """异步数据库会话"""
    session_factory = database_manager.get_async_session_factory()
    async with session_factory() as session:
        try:
            yield session
        finally:
            await session.rollback()


@pytest.fixture
def db_session(database_manager) -> Generator:
    """同步数据库会话"""
    session_factory = database_manager.get_session_factory()
    session = session_factory()
    try:
        yield session
    finally:
        session.rollback()
        session.close()


# ======================================
# 🔄 Redis 测试配置
# ======================================

@pytest.fixture(scope="session")
def redis_config():
    """Redis测试配置"""
    return {
        'host': os.getenv('REDIS_HOST', 'localhost'),
        'port': int(os.getenv('REDIS_PORT', '6379')),
        'password': os.getenv('REDIS_PASSWORD', 'redfire_redis_2025'),
        'db': int(os.getenv('REDIS_DB', '1')),  # 使用数据库1进行测试
        'decode_responses': True
    }


# ======================================
# 🧪 测试数据管理
# ======================================

@pytest.fixture(autouse=True)
async def cleanup_test_data(async_db_session):
    """自动清理测试数据"""
    yield
    # 测试后清理
    if os.getenv('TEST_DATA_CLEANUP', 'true').lower() == 'true':
        # 这里可以添加清理逻辑
        await async_db_session.rollback()


@pytest.fixture(scope="session")
def event_loop():
    """创建事件循环"""
    loop = asyncio.new_event_loop()
    yield loop
    loop.close()


# ======================================
# 🔧 测试工具
# ======================================

@pytest.fixture
def mock_tushare():
    """模拟Tushare API"""
    return MagicMock()


@pytest.fixture
def mock_cache():
    """模拟缓存"""
    return MagicMock()


# ======================================
# 📊 测试标记
# ======================================

def pytest_configure(config):
    """配置pytest标记"""
    config.addinivalue_line(
        "markers", "integration: marks tests as integration tests"
    )
    config.addinivalue_line(
        "markers", "unit: marks tests as unit tests"
    )
    config.addinivalue_line(
        "markers", "slow: marks tests as slow running"
    )
    config.addinivalue_line(
        "markers", "database: marks tests that require database"
    )
    config.addinivalue_line(
        "markers", "redis: marks tests that require redis"
    )
